package com.lili.service.impl;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.lili.mapper.*;
import com.lili.pojo.*;
import com.lili.service.QuestionPracticeService;
import com.lili.vo.request.troop.*;
import com.lili.vo.response.troop.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;

@Service
public class QuestionPracticeServiceImpl extends ServiceImpl<QuestionPracticeMapper, QuestionPractice>
        implements QuestionPracticeService {

    private QuestionMapper questionMapper;
    private WrongMapper wrongMapper;

    @Autowired
    public QuestionPracticeServiceImpl(QuestionMapper questionMapper, WrongMapper wrongMapper) {
        this.questionMapper = questionMapper;
        this.wrongMapper = wrongMapper;
    }

    /**
     * 对练习列表首页的查询
     *
     * @param vo
     * @return
     */
    @Override
    public IPage<PracticeListRespVO> selectPracticeList(QueryReqVO vo) {
        IPage<PracticeListRespVO> page = new Page<>(vo.getPageIndex(), vo.getPageSize());
        return baseMapper.selectPracticeList(page, vo);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public List<AnswerCardRespVO> selectCard(Integer subjectId, Integer userId) {
        int num = questionMapper.getNUm(subjectId);
        int havNum = questionMapper.getHavNum(subjectId, userId);
        if (havNum >= num) {
            ArrayList<AnswerCardRespVO> list = new ArrayList<>();
            List<Integer> ids = questionMapper.getIds(subjectId);
            final int[] count = {1};
            ids.forEach(item -> {
                AnswerCardRespVO answerCardRespVO = new AnswerCardRespVO();
                answerCardRespVO.setQuestionId(item);
                answerCardRespVO.setCorrect(null);
                answerCardRespVO.setItemOrder(count[0]);
                count[0]++;
                list.add(answerCardRespVO);
            });
            return list;
        } else {
            //先得到答题卡应该有的数据(题目Id)
            List<Integer> idList = questionMapper.selectIdList(subjectId);
            // 得到用户答题卡中的数据
            AtomicInteger order = new AtomicInteger(1);
            List<AnswerCardRespVO> cardRespVOS = idList.stream().map(item -> {
                AnswerCardRespVO vo = new AnswerCardRespVO();
                vo.setQuestionId(item);
                Boolean flag = baseMapper.selectUserAnswerCard(item, userId);
                vo.setCorrect(flag);
                vo.setItemOrder(order.getAndIncrement());
                return vo;
            }).collect(Collectors.toList());
            return cardRespVOS;
        }
    }

    /**
     * 查询练习列表的题目
     *
     * @param vo
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public PracticeQuestionRespVO selectPracticeQuestion(PracticeQuesReqVO vo) {
        Integer questionId = vo.getQuestionId();
        if (Objects.isNull(questionId)) {
            questionId = questionMapper.selectStartId(vo.getSubjectId());
        }
        PracticeQuestionRespVO model = questionMapper.getVO(vo.getSubjectId(), questionId);
        return model;
    }

    /**
     * 对练习的答案的批改
     *
     * @param vo
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean correctQuestion(PracticeQuestionRespVO vo, Integer createUser) {
        QuestionPractice practice = new QuestionPractice();
        practice.setPracticeAnswer(vo.getPracticeAnswer());
        practice.setQuestionId(vo.getId());
        practice.setCreateUser(createUser);
        practice.setSubjectId(vo.getSubjectId());
        Boolean flag = isCorrect(vo);
        // 如果是错题，那么加入错题库中
        if (!flag) {
            // 进行查询，看是否存在该数据
            Wrong wrong = wrongMapper.selectByQuestionIdAndCreateUser(practice.getQuestionId(), createUser);
            Wrong one = getWrong(practice, createUser);
            if (Objects.isNull(wrong)) {
                wrongMapper.insert(one);
            } else {
                one.setId(wrong.getId());
                wrongMapper.updateById(one);
            }
        }
        practice.setCorrect(0);
        baseMapper.insert(practice);
        return flag;
    }

    private Boolean isCorrect(PracticeQuestionRespVO vo) {
        if (vo.getCorrectAnswer().equals(vo.getPracticeAnswer())) {
            return true;
        }
        return false;
    }

    private Wrong getWrong(QuestionPractice practice, Integer createUser) {
        Wrong wrong = new Wrong();
        wrong.setQuestionId(practice.getQuestionId());
        wrong.setSubjectId(practice.getSubjectId());
        wrong.setCreateUser(createUser);
        wrong.setAnswer(practice.getPracticeAnswer());
        return wrong;
    }


}
